/**
 * Execute the user's code.
 * Just a quick and dirty eval.  No checks for infinite loops, etc.
 */
function runJS() {
  var code = Blockly.Generator.workspaceToCode('JavaScript');
  try {
    eval(code);
  } catch (e) {
    alert('Program error:\n' + e);
  }
}

/**
 * Backup code blocks to localStorage.
 */
function backup_blocks() {
  if ('localStorage' in window) {
    var xml = Blockly.Xml.workspaceToDom(Blockly.mainWorkspace);
    window.localStorage.setItem('arduino', Blockly.Xml.domToText(xml));
  }
}

/**
 * Restore code blocks from localStorage.
 */
function restore_blocks() {
  if ('localStorage' in window && window.localStorage.arduino) {
    var xml = Blockly.Xml.textToDom(window.localStorage.arduino);
    Blockly.Xml.domToWorkspace(Blockly.mainWorkspace, xml);
  }
}

/**
* Save Arduino generated code to local file.
*/
function saveCode() {
  var fileName = window.prompt('What would you like to name your file?', 'BlocklyDuino')
  //doesn't save if the user quits the save prompt
  if(fileName){
    var blob = new Blob([Blockly.Arduino.workspaceToCode()], {type: 'text/plain;charset=utf-8'});
    saveAs(blob, fileName + '.ino');
  }
}


/*
* 打成一个压缩包
* @metas_zip是一个object key是文件名  value是文件内容
* @filename是压缩包的名字
* */
function metas_save_zip(metas_zip,filename){

     var zip = new JSZip();
    for(var i in metas_zip){
        zip.file(i,metas_zip[i])
    }

    zip.generateAsync({type:"blob"}).then(function(content) {
    // Force down of the Zip file
    saveAs(content, filename);
    });
}

/**
 * Save blocks to local file.
 * better include Blob and FileSaver for browser compatibility
 */
function save() {
  var xml = Blockly.Xml.workspaceToDom(Blockly.mainWorkspace);
  var data = Blockly.Xml.domToText(xml);
//  var fileName = window.prompt('是否保存工程文件，文件名?', 'BlocklyDuino');
    var character_data=getSaveConfig(true);
  var metas_zip=new Object();
  metas_zip["blocks.xml"]=data;
    metas_zip["character"]=character_data;
  var zip_filename="MRC_offile.mt";
    metas_save_zip(metas_zip,zip_filename);

//  if(fileName){
//    var blob = new Blob([data], {type: 'text/xml'});
//    saveAs(blob, fileName + ".xml");
//  }
}

/**
 * Load blocks from local file.
 */
function load(event) {
    var block_xml = "";
    var new_zip = new JSZip();
    var project_name=this.files[0]
    new_zip.loadAsync(this.files[0]).then(function (zip) {
        new_zip.file("blocks.xml").async("string")
            .then(function (content) {
                // use content
                block_xml = content;
                if(block_xml!=""){
                     try {
                    var xml = Blockly.Xml.textToDom(block_xml);
                } catch (e) {
                    alert($.i18n.prop('js_load_project_error'));
                    return;
                }
                var count = Blockly.mainWorkspace.getAllBlocks().length;
                if (count && confirm('Replace existing blocks?\n"Cancel" will merge.')) {
                    Blockly.mainWorkspace.clear();
                }
                Blockly.Xml.domToWorkspace(Blockly.mainWorkspace, xml);
                project_name=project_name.name.split(".")[0];
                $("#project_name").text(project_name);
                $("#project_name").css("display","block");
                }

            }
        );
         new_zip.file("character").async("string")
            .then(function (content) {
                initByConfig(content,true);
             });
    });
}



/* 加载工程样例*/
function get_example_project(ele) {
  var file_data=null;
  var file_name=$(ele).text();
  $.ajax({
      url: "http://"+window.location.host+"/get_example_project/?name="+file_name,
      type: "Get",
      async: false,
      dataType: "json",
      error: function (XMLHttpRequest, textStatus, errorThrown) {
        // alert("error!" + errorThrown);

      },
      success: function (data) {
        // var parse_data=JSON.parse(data);
        file_data=data;
      }
    });
  var block_xml = file_data['blocks.xml'];
  var project_name=file_data['project_name'];
  if(block_xml!=""){
       try {
        var xml = Blockly.Xml.textToDom(block_xml);
      } catch (e) {
        alert($.i18n.prop('js_load_project_error'));
      return;
      }
      var count = Blockly.mainWorkspace.getAllBlocks().length;
       Blockly.mainWorkspace.clear();
      Blockly.Xml.domToWorkspace(Blockly.mainWorkspace, xml);
      $("#project_name").text(project_name);
      $("#project_name").css("display","block");
  }
}



/*新建一个空的工程，初始blocks和人物 背景*/
function new_empty_project() {
  var empty_figure_active='{"backgrounds":[],"humans":["./img/human/753c35deaf4b507f.png","./img/human/5f1decb5302f330b.png"],"currentBg":"./img/juxingkuang.png","currentHm":"./img/human/753c35deaf4b507f.png"}';
  if(confirm($.i18n.prop('js_new_project_tip'))){
    Blockly.mainWorkspace.clear();
    $("#project_name").text('');
    $("#project_name").css("display","none");
    initByConfig(empty_figure_active,true);
    ActionBlock.isAction();
    ActionBlock.reset();
  }
}

/**
 * Discard all blocks from the workspace.
 */
function discard() {
  var count = Blockly.mainWorkspace.getAllBlocks().length;
    if(confirm($.i18n.prop('js_clear_block_tip'))) {
        if (count < 2 || window.confirm('Delete all ' + count + ' blocks?')) {
            Blockly.mainWorkspace.clear();
            renderContent();
        }
    }
}

/*
 * auto save and restore blocks
 */
function auto_save_and_restore_blocks() {
  // Restore saved blocks in a separate thread so that subsequent
  // initialization is not affected from a failed load.
  window.setTimeout(restore_blocks, 0);
  // Hook a save function onto unload.
  bindEvent(window, 'unload', backup_blocks);
  tabClick(selected);

  // Init load event.
  var loadInput = document.getElementById('load');
  loadInput.addEventListener('change', load, false);
  document.getElementById('fakeload').onclick = function() {
    loadInput.click();
  };
}

/**
 * Bind an event to a function call.
 * @param {!Element} element Element upon which to listen.
 * @param {string} name Event name to listen to (e.g. 'mousedown').
 * @param {!Function} func Function to call when event is triggered.
 *     W3 browsers will call the function with the event object as a parameter,
 *     MSIE will not.
 */
function bindEvent(element, name, func) {
  if (element.addEventListener) {  // W3C
    element.addEventListener(name, func, false);
  } else if (element.attachEvent) {  // IE
    element.attachEvent('on' + name, func);
  }
}

//loading examples via ajax
var ajax;
function createAJAX() {
  if (window.ActiveXObject) { //IE
    try {
      return new ActiveXObject("Msxml2.XMLHTTP");
    } catch (e) {
      try {
        return new ActiveXObject("Microsoft.XMLHTTP");
      } catch (e2) {
        return null;
      }
    }
  } else if (window.XMLHttpRequest) {
    return new XMLHttpRequest();
  } else {
    return null;
  }
}

function onSuccess() {
  if (ajax.readyState == 4) {
    if (ajax.status == 200) {
      try {
      var xml = Blockly.Xml.textToDom(ajax.responseText);
      } catch (e) {
        alert('Error parsing XML:\n' + e);
        return;
      }
      var count = Blockly.mainWorkspace.getAllBlocks().length;
      if (count && confirm('Replace existing blocks?\n"Cancel" will merge.')) {
        Blockly.mainWorkspace.clear();
      }
      Blockly.Xml.domToWorkspace(Blockly.mainWorkspace, xml);
    } else {
      alert("Server error");
    }
  }
}

function load_by_url(uri) {
  ajax = createAJAX();
  if (!ajax) {
　　   alert ('Not compatible with XMLHttpRequest');
　　   return 0;
　  }
  if (ajax.overrideMimeType) {
    ajax.overrideMimeType('text/xml');
  }

　　ajax.onreadystatechange = onSuccess;
　　ajax.open ("GET", uri, true);
　　ajax.send ("");
}

function uploadCode(code, callback) {
    var target = document.getElementById('content_arduino');
    var spinner = new Spinner().spin(target);

    var url = "http://"+window.location.host+'/';
    var method = "POST";

    // You REALLY want async = true.
    // Otherwise, it'll block ALL execution waiting for server response.
    var async = true;

    var request = new XMLHttpRequest();

    request.onreadystatechange = function() {
        if (request.readyState != 4) {
            return;
        }

        spinner.stop();

        var status = parseInt(request.status); // HTTP response status, e.g., 200 for "200 OK"
        var errorInfo = null;
        switch (status) {
        case 200:
            break;
        case 0:
            errorInfo = "code 0\n\nCould not connect to server at " + url + ".  Is the local web server running?";
            break;
        case 400:
            errorInfo = "code 400\n\n"+$.i18n.prop('js_upload_code_400');
            break;
        case 500:
            errorInfo = "code 500\n\n"+$.i18n.prop('js_upload_code_500');
            break;
        case 501:
            errorInfo = "code 501\n\nUpload failed.  Is 'ino' installed and in your path?  This only works on Mac OS X and Linux at this time.";
            break;
        default:
            errorInfo = "code " + status + "\n\nUnknown error.";
            break;
        };

        callback(status, errorInfo);
    };

    request.open(method, url, async);
    request.setRequestHeader("Content-Type", "text/plain;charset=utf-8");
    request.send(code);
}

function uploadClick() {
    var code = Blockly.Arduino.workspaceToCode();

    var xmlDom = Blockly.Xml.workspaceToDom(Blockly.mainWorkspace);
    var xmlText = Blockly.Xml.domToPrettyText(xmlDom);

    var json_data=new Object();
    json_data["arduino_code"]=code;
    json_data["xml"]=xmlText;
    json_data["block_count"]=workspace.getAllBlocks().length;
    json_data["user_edit"]=1;
    var new_code=JSON.stringify(json_data);
    if(confirm($.i18n.prop('js_mrc_burning_tip'))) {
        uploadCode(new_code, function (status, errorInfo) {
            if (status == 200) {
                refresh_history();
                alert($.i18n.prop('js_mrc_burning_success'));
            } else {
                alert($.i18n.prop('js_mrc_burning_error') + errorInfo);
            }
        });
    }
}

function resetClick() {
     var code = "void setup() {} void loop() {}";
     var xmlDom = Blockly.Xml.workspaceToDom(Blockly.mainWorkspace);
    var xmlText = Blockly.Xml.domToPrettyText(xmlDom);

    var json_data=new Object();
    json_data["arduino_code"]=code;
    json_data["xml"]=xmlText;
    json_data["block_count"]=workspace.getAllBlocks().length;
    json_data["user_edit"]=0;
    var new_code=JSON.stringify(json_data);

    if(confirm($.i18n.prop('js_mrc_reset_tip'))) {
        uploadCode(new_code, function (status, errorInfo) {
            if (status == 200) {
                alert($.i18n.prop('js_mrc_reset_success'));
            } else {
                alert($.i18n.prop('js_mrc_reset_error') + errorInfo);
            }
        });
    }
}


/*启动加载默认工程*/
function load_default_example_project() {
  var file_data=null;
  var file_name=$.i18n.prop('example_crazy_maze');
  $.ajax({
      url: "http://"+window.location.host+"/get_example_project/?name="+file_name,
      type: "Get",
      async: false,
      dataType: "json",
      error: function (XMLHttpRequest, textStatus, errorThrown) {
        // alert("error!" + errorThrown);

      },
      success: function (data) {
        // var parse_data=JSON.parse(data);
        file_data=data;
      }
    });
  var block_xml = file_data['blocks.xml'];
  var project_name=file_data['project_name'];
  if(block_xml!=""){
       try {
        var xml = Blockly.Xml.textToDom(block_xml);
      } catch (e) {
        alert($.i18n.prop('js_load_project_error'));
      return;
      }
      var count = Blockly.mainWorkspace.getAllBlocks().length;
       Blockly.mainWorkspace.clear();
      Blockly.Xml.domToWorkspace(Blockly.mainWorkspace, xml);
      $("#project_name").text(project_name);
      $("#project_name").css("display","block");
  }
}
